package utils;

import entity.WordNode;
import org.apache.commons.lang.StringUtils;

import java.io.FileWriter;
import java.io.IOException;
import java.util.Map;
import java.util.Set;
import java.util.concurrent.TimeUnit;

/**
 * @author tianjiashu
 * @Description
 * @create 2023/2/22 11:24
 */
public class Trie {

    private final WordNode root;
    private FileWriter fileWriter;


    public Trie() {
        root = new WordNode();
    }

    public void insert(Map.Entry<String, String> entry) {
        String aliasName = entry.getValue();
        String fullName = entry.getKey();
        WordNode node = root;
        for (int i = aliasName.length() - 1; i >= 0; i--) {
            char c = aliasName.charAt(i);
            if (!node.getChilds().containsKey(c)) {
                node.getChilds().put(c, new WordNode());
            }
            node = node.getChilds().get(c);
        }
        node.setAliasName(aliasName);
        node.setFullName(fullName);
        node.end();
    }

    public boolean search(String word) {
        WordNode node = root;
        for (int i = word.length() - 1; i >= 0; i--) {
            char c = word.charAt(i);
            if (!node.getChilds().containsKey(c)) {
                return false;
            }
            node = node.getChilds().get(c);
        }
        node.incrIfEnd();
        return node.isEnd();
    }

    public String startsWith(String prefix) {
        WordNode node = root;
        for (int i = prefix.length() - 1; i >= 0; i--) {
            char c = prefix.charAt(i);
            if (!node.getChilds().containsKey(c)) {
                return null;
            }
            node = node.getChilds().get(c);
        }
        return node.getAliasName();
    }

    public WordNode getRoot() {
        return root;
    }

    public void statistcal(String docId,String docBody) {


        // 待检测文字为空
        if (StringUtils.isEmpty(docBody)) {
            return;
        }

        // 没有关键词
        if (root.getChildsSet() == null) {
            return;
        }
        Map<Character, WordNode> childs = root.getChilds();
        char[] chars = docBody.toCharArray();
        for (int i = chars.length-1; i >=0 ; i--) {
            char word = chars[i];
            WordNode head = childs.get(word);

            if (head == null) {
                continue;
            }
            WordNode child = head;

            for (int k = i - 1; k >=0 ; k--) {
                char childWord = chars[k];
                // 跳过符号等特殊字符
                if (isSkip(childWord)) {
                    continue;
                }

                if (child.getChilds() == null) {
                    break;
                }

                child = child.getChilds().get(childWord);
                if (child == null) {
                    break;
                }
                if (child.isEnd()) {
                    child.add(docId);
                    child.incrCount();
                }
            }
        }
    }

    private boolean isSkip(char firstChar) {
        // 过滤空格(32)及不可见字符
        if (firstChar <= ' ') {
            return true;
        }
        // 过滤删除符
        return firstChar == 127;
    }

    public void saveResult() throws IOException, InterruptedException {
        fileWriter = new FileWriter("result.txt",false);
        dfs(root);
    }

    private void dfs(WordNode node) throws IOException {
        if(node.isEnd()){
            long sum = node.getCount().longValue();
            if(sum > 0){
                fileWriter.write(node.toOneLine());
                fileWriter.flush();
            }
        }
        Map<Character, WordNode> childs = node.getChilds();
        for (Character character : childs.keySet()) {
            dfs(childs.get(character));
        }
    }

}
